import * as fs from "fs";
import * as path from "path";
import { parseJson } from "@dcloudio/uni-cli-shared";

function normalizeUniModulesPagesJson(
  pagesJson: { pages: any[]; subPackages: any[] },
  pluginId: string
) {
  if (Array.isArray(pagesJson.pages)) {
    pagesJson.pages.forEach((page: { path: string }) => {
      page.path = "uni_modules/" + pluginId + "/" + page.path;
    });
  }
  if (Array.isArray(pagesJson.subPackages)) {
    pagesJson.subPackages.forEach((subPackage: { root: string }) => {
      subPackage.root = "uni_modules/" + pluginId + "/" + subPackage.root;
    });
  }
  return pagesJson;
}

function logger(data: any, path = "log.stdout.log") {
  const options = {
    flags: "w",
    encoding: "utf8" as BufferEncoding,
  };
  const stderr = fs.createWriteStream(path, options);
  const myConsole = new console.Console(stderr);
  myConsole.log(data);
}

export interface UniModulePagesOption {
  dir?: string;
  uniModules?: { id: string; path: string }[];
}

export default class UniModulePages {
  routerDir: string | undefined;
  routerFiles: { id: string; path: string }[] | undefined;
  constructor(option: UniModulePagesOption) {
    let { dir, uniModules } = option;
    if (dir) {
      dir = path.resolve(process.env.UNI_INPUT_DIR as string, dir);
    }
    if (uniModules) {
      uniModules = uniModules.map((module) => {
        return {
          ...module,
          path: path.resolve(
            process.env.UNI_INPUT_DIR as string,
            `uni_modules/${module.id}/${module.path}`
          ),
        };
      });
    }
    this.routerDir = dir;
    this.routerFiles = uniModules;
  }
  getPageJson(addDependency: (arg0: string) => void) {
    // router路由注入
    const routerDir = this.routerDir;
    const routerPagesJson = {
      pages: [] as any,
      subPackages: [] as any[],
    };
    if (routerDir && fs.existsSync(routerDir)) {
      let files = fs.readdirSync(routerDir);
      files = files.filter((f) => {
        return f.endsWith(".json");
      });
      for (const file of files) {
        const routerPath = path.resolve(routerDir, file);
        const routerJson: typeof routerPagesJson = parseJson(
          fs.readFileSync(routerPath).toString(),
          true
        );
        addDependency(routerPath);
        routerPagesJson.pages.push(...(routerJson.pages || []));
        routerPagesJson.subPackages.push(...(routerJson.subPackages || []));
      }
    }

    // uni_modules路由注入
    const routerFiles = this.routerFiles;
    const uniModulesPagesJson = {
      pages: [] as any[],
      subPackages: [] as any[],
    };

    routerFiles?.forEach((routerFile) => {
      if (fs.existsSync(routerFile.path)) {
        const pagesJson: typeof uniModulesPagesJson =
          normalizeUniModulesPagesJson(
            parseJson(fs.readFileSync(routerFile.path).toString(), true),
            routerFile.id
          );
        addDependency(routerFile.path);
        uniModulesPagesJson.pages.push(...(pagesJson.pages || []));
        uniModulesPagesJson.subPackages.push(...(pagesJson.subPackages || []));
      }
    });

    return {
      pages: [...routerPagesJson.pages, ...uniModulesPagesJson.pages],
      subPackages: [
        ...routerPagesJson.subPackages,
        ...uniModulesPagesJson.subPackages,
      ],
    };
  }
  loader(
    pagesJson: { pages: any[]; subPackages: any[] },
    { addDependency }: any
  ) {
    const { pages = [], subPackages = [] } = this.getPageJson(addDependency);
    pagesJson.pages = pagesJson.pages || [];
    pagesJson.subPackages = pagesJson.subPackages || [];
    pagesJson.pages.push(...pages);
    pagesJson.subPackages.push(...subPackages);
    return pagesJson;
  }
}
